package com.gurid.service.trade.service.impl;

import com.gurid.common.base.result.ResultCode;
import com.gurid.common.base.util.ExceptionUtils;
import com.gurid.common.base.util.HttpClientUtils;
import com.gurid.service.base.exception.GuridException;
import com.gurid.service.trade.entity.Order;
import com.gurid.service.trade.service.OrderService;
import com.gurid.service.trade.service.WeixinPayService;
import com.gurid.service.trade.util.WeixinPayProperties;
import com.github.wxpay.sdk.WXPayUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.Map;

@Service
@Slf4j
public class WeixinPayServiceImpl implements WeixinPayService {

    @Autowired
    private OrderService orderService;
    @Autowired
    private WeixinPayProperties payProperties;

    @Override
    public Map<String, Object> createNative(String orderNo, String remoteAddr) {

        //根据订单号获取订单
        Order order = orderService.getOrderByOrderNo(orderNo);
        //调用微信的统一下单api
        HttpClientUtils client = new HttpClientUtils("https://api.mch.weixin.qq.com ");
        //组装参数
        Map<String, String> params = new HashMap<>();
        params.put("appid", payProperties.getAppId());//公众号id
        params.put("mch_id", payProperties.getPartner());//商户号
        params.put("nonce_str", WXPayUtil.generateNonceStr());//随机数
        params.put("body", order.getCourseTitle());//商品描述
        params.put("out_trade_no", orderNo);//商户系统内部订单号，只能是数字、大小写字母_-*且在同一个商户号下唯一。
        params.put("total_fee", order.getTotalFee().intValue()+"");//订单金额，单位是分
        params.put("spbill_create_ip", remoteAddr);//终端IP
        params.put("notify_url", payProperties.getNotifyUrl());//异步接收微信支付结果通知的回调地址，通知URL必须为外网可访问的URL，不能携带参数。 公网域名必须为HTTPS，如果是走专线接入，使用专线NAT IP或者私有回调域名可使用HTTP
        params.put("trade_type", "NATIVE");//交易类型

        try {
            //将参数转化位xml，并追加计算的签名
            String xmlParams = WXPayUtil.generateSignedXml(params, payProperties.getPartnerKey());
            log.info(xmlParams);

            //将参数放入请求对象的方法体
            client.setXmlParam(xmlParams);
            //使用post方式发送请求
            client.post();
            //获取响应
            String resultXml = client.getContent();
            log.info("resultXml: {}", resultXml);

            //解析XML
            Map<String, String> resultMap = WXPayUtil.xmlToMap(resultXml);
            if ("FAIL".equals(resultMap.get("return_code")) || "FAIL".equals(resultMap.get("return_code"))) {

                log.error("微信支付统一下单错误 → \n" +
                        "return_code: " + resultMap.get("return_code") + "\n" +
                        "return_msg: " + resultMap.get("return_msg") + "\n" +
                        "result_code: " + resultMap.get("result_code") + "\n" +
                        "err_code: " + resultMap.get("err_code") + "\n" +
                        "err_code_des: " + resultMap.get("err_code_des"));
                throw new GuridException(ResultCode.PAY_UNIFIED_ERROR);
            }

            //最后要组装的内容
            HashMap<String, Object> map = new HashMap<>();
            map.put("return_code", resultMap.get("return_code"));
            map.put("code_url", resultMap.get("code_url"));//二维码url
            map.put("course_id", order.getCourseId());//课程id
            map.put("total_fee", order.getTotalFee());//订单金额
            map.put("out_trade_no", orderNo);//订单号

            return null;

        } catch (Exception e) {
            log.error(ExceptionUtils.getMessage(e));
            throw new GuridException(ResultCode.PAY_UNIFIED_ERROR);
        }
    }
}
